<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>3D Quaternion Rotation</title>
  <style>
    body {
      margin: 0;
    }

    canvas {
      display: block;
    }
  </style>
</head>

<body>
  <script src="https://cdn.jsdelivr.net/npm/three@0.135.0/build/three.min.js"></script>

  <script>
    // Set up scene, camera, and renderer
    const scene = new THREE.Scene();
    const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
    const renderer = new THREE.WebGLRenderer();
    renderer.setSize(window.innerWidth, window.innerHeight);
    document.body.appendChild(renderer.domElement);

    // Create a cube (representing an object)
    const geometry = new THREE.BoxGeometry();
    const material = new THREE.MeshBasicMaterial({ color: 0x00ff00 });
    const cube = new THREE.Mesh(geometry, material);
    scene.add(cube);

    // Position camera
    camera.position.z = 5;

    // Function to rotate using quaternion
    function rotateQuaternion (cube, angle, axis) {
      const quaternion = new THREE.Quaternion();
      quaternion.setFromAxisAngle(axis, angle); // Set quaternion from axis and angle
      cube.applyQuaternion(quaternion); // Apply quaternion rotation
    }

    let angle = 0;

    // Animation loop
    function animate () {
      requestAnimationFrame(animate);

      // Rotate the cube
      const axis = new THREE.Vector3(1, 1, 0).normalize(); // Rotation axis (diagonal)
      rotateQuaternion(cube, angle, axis);

      // Render the scene
      renderer.render(scene, camera);

      angle += 0.01; // Increment angle for continuous rotation
    }

    animate();
  </script>
</body>

</html>